﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Data.Interfaces.Callback;
using Data.Characters;
using LeagueOfRila.Model;
using Data;
using System.Threading;

namespace LeagueOfRila.Callback
{
    class CPlayerService : ICPlayerService
    {
        public GameModel gm;

        public void updateOtherPlayer(string pseudo, string classePerso, int posX, int posY, int orientation, int step, int life, int mana)
        {
            bool playerfound = false;
            foreach (Player otherPlayer in this.gm.otherPlayers)
            {
                if (otherPlayer.pseudo.ToString() == pseudo)
                {
                    otherPlayer.character.name = classePerso;
                    otherPlayer.posX = posX;
                    otherPlayer.posY = posY;
                    otherPlayer.orientation = orientation;
                    otherPlayer.step = step;
                    otherPlayer.character.life = life;
                    otherPlayer.character.mana = mana;
                    playerfound = true;
                }
            }
            if (!playerfound)
            {
                Player otherPlayer = new Player(pseudo);
                switch (classePerso)
                {
                    case "Priest":
                        otherPlayer.character = new Priest();
                        break;

                    case "War":
                        otherPlayer.character = new War();
                        break;

                    case "Mage":
                        otherPlayer.character = new Mage();
                        break;

                    case "Matthieu":
                        otherPlayer.character = new Matthieu();
                        break;
                }
                otherPlayer.posX = posX;
                otherPlayer.posY = posY;
                otherPlayer.orientation = orientation;
                otherPlayer.step = step;
                otherPlayer.character.life = life;
                otherPlayer.character.mana = mana;

                this.gm.otherPlayers.Add(otherPlayer);
                this.gm.AddTexturePlayer(otherPlayer.pseudo, otherPlayer.character.sprite);

            }

        }

        public void updateOtherAnimation(string pseudo, int posX, int posY, string attackType, int orientation)
        {
            lock (this.gm.GetView().lockAnim)
            {
                this.gm.GetView().lockAnimActive = true;
                foreach (Player otherPlayer in this.gm.otherPlayers)
                {
                    if (otherPlayer.pseudo.ToString() == pseudo && pseudo != Client.player.pseudo)
                    {
                        Animation anim = new Animation(attackType, otherPlayer, (int)this.gm.GetView().mapOrigin.X, (int)this.gm.GetView().mapOrigin.Y);

                        bool animFound=false;
                        foreach(Animation animation in this.gm.GetView().animations)
                        {
                            if (animation.type == attackType && pseudo == animation.player.pseudo)
                                animFound = true;
                        }

                        if(!animFound)
                            this.gm.GetView().animations.Add(anim);
                    }

                }
                this.gm.GetView().lockAnimActive = false;
            }
        }
        public void updateCurrentPlayerLife(string pseudo, int life, int damage)
        {
            Player player = null;

            if (Client.player.pseudo == pseudo)
            {
                Client.player.character.life = life;
            }

            if (Client.player.character.life == 0)
            {
                Thread respawnThread = new Thread(() =>
                {
                    Thread.Sleep(2000);
                    this.gm.currentMap.GetSpawnPosition(ref Client.player.posX, ref Client.player.posY, ref this.gm.GetView().mapOrigin.X, ref this.gm.GetView().mapOrigin.Y, this.gm.GetView().GraphicsDevice.Viewport.Width, this.gm.GetView().GraphicsDevice.Viewport.Height);
                    //Remise à 0 des caractéristiques du player
                    Client.player.character.life = Client.player.character.maxLife;
                    Client.player.character.mana = Client.player.character.maxMana;
                });
                respawnThread.Start();
            }

            if(pseudo == Client.player.pseudo)
            {
                player = Client.player;
            }
            else
            {
                foreach (Player currentPlayer in this.gm.otherPlayers)
                {
                    if (currentPlayer.pseudo == pseudo)
                    {
                        player = currentPlayer;
                    }
                }
            }

            Animation anim = new Animation("damage", player, (int)this.gm.GetView().mapOrigin.X, (int)this.gm.GetView().mapOrigin.Y);
            anim.damage = damage;
            bool animFound = false;
            foreach (Animation animation in this.gm.GetView().animations)
            {
                if (animation.type == "damage" && pseudo == animation.player.pseudo)
                    animFound = true;
            }

            lock (this.gm.GetView().lockAnim)
            {
                this.gm.GetView().lockAnimActive = true;
                if (!animFound)
                    this.gm.GetView().animations.Add(anim);
                this.gm.GetView().lockAnimActive = false;
            }
        }

        public void updatePlayerScore(string pseudo, int death, int score)
        {
            if (Client.player.pseudo == pseudo)
            {
                Client.player.death = death;
                Client.player.score = score;
            }
            else
            {
                foreach (Player player in this.gm.otherPlayers)
                {
                    if (player.pseudo == pseudo)
                    {
                        player.death = death;
                        player.score = score;
                    }
                }
            }
        }

        public void regenStats()
        {
            //regen life
            if (Client.player.character.life > 0 && Client.player.character.life < Client.player.character.maxLife)
            {
                Client.player.character.life = Client.player.character.life + 100;
                if (Client.player.character.life > Client.player.character.maxLife)
                    Client.player.character.life = Client.player.character.maxLife;
            }
            //regen mana
            if (Client.player.character.maxMana > 0 && Client.player.character.mana < Client.player.character.maxMana)
            {
                Client.player.character.mana = Client.player.character.mana + 100; 
                if (Client.player.character.mana > Client.player.character.maxMana)
                    Client.player.character.mana = Client.player.character.maxMana;
            }

            this.gm.tellServerCharInfos();            

        }

    }
}
